Printable representations are useful for debugging purposes. Be careful when using an object's printable representation to refer to that object-the object's printable representation may not be the same thing you would type into a script to create or query that object.
ScriptX defines a default stream named debug
for printable representations. In some ScriptX environments, the debug stream may be attached to a listener or debugging window. You can also create additional streams and use them as the stream argument to each of the functions described in this section.
print
on it. The print
global function writes a representation of the object to the debug
stream. This form of printing is used extensively in examples throughout this book.t := new Rect
print t
[0, 0, 0, 0] as Rect
r := new LinkedList
print r
#() as LinkedList
The function call print "t"
appears to have the same output in the
Listener window as the simply typing the string literal "t"
, followed by a
newline character. The difference is that the print
function actually prints to a
stream, the debug
stream, which can be directed to the Listener window, or to
another window, such as a debugger.
You can do simple formatted output by coercing the printable representation of any object into a string, adding it to another string as a label, and then printing the result:
print ("r contains: " + (r as String))
"r contains #() as LinkedList"
prin
. Many classes in the ScriptX core classes implement a prin
method; prin
is commonly specialized by scripted classes.prin
objectToPrint option stream
where:ByteStream
, or one of its subclasses.
prin
method prints objectToPrint to stream using the specified option without including a newline character at the end of the line.See the "Streams" chapter of ScriptX Components Guide and the ScriptX Class Reference for more information about streams.
Unlike the print
function, which is a global function that is not associated with any class, prin
is a generic function. It is defined as a method by the root system class, RootObject
, and can be specialized by any class in the system that requires a special printed representation. The prin
generic function is used as a primitive by all other printing functions, most of which, like print
, are global functions. By specializing prin
for a class, you can assure that all ScriptX printing functions can print that class. (In certain classes that contain recursive structures, it is necessary to specialize the recurPrin
generic function as well.)
By default, ScriptX provides only one appropriate stream for printable information-the debugging stream, referenced by the system global variable debug
. Streams can also be instances of the class String
or a stream that you have created yourself.
The option argument to prin
may be one of the following names. Some classes, notably the Exception
classes, define other options available to prin
, but at least these four must be available:
@normal
prints a "regular" representation of the object.
@complete
prints a complete representation which may include more information than @normal
, depending on the class. In collections such as Array
, for example, the @normal
representation only prints the first ten elements. The @complete
representation prints all the elements.
@debug
prints even more information suitable for debugging purposes, including the class of the object, or in the case of collections such as arrays, the class of the collection and the classes of each of its items.
@unadorned
prints a plain representation of the object, which may vary depending on the class. For example, it prints an instance of String
without quote characters as delimiters. It prints a name literal, a NameClass
object, without the identifying "@
" sign.
prin
expression itself:a := "test string"
prin a @normal debug
"test string"
prin a @debug debug
StringConstant: "test string"
prin a @unadorned debug
test string
t := #(1,2,3,4)
prin t @normal debug
#(1, 2, 3, 4)
prin t @unadorned debug
1234
prin t @debug debug
Array@0x3904e8: #(ImmediateInteger: 1, ImmediateInteger: 2,
ImmediateInteger: 3, ImmediateInteger: 4)
t := #(1,2,3,4,5,6,7,8,9,10,11,12,13,14,15)
prin t @normal debug -- default is only 10 elements
#(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, ...)
prin t @complete debug -- @complete prints all the elements
#(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15)
prin
is used by several global functions, summarized here, which can be used as shortcuts to the prin
generic. Printing functions are described in detail in the "Global Functions" chapter of the ScriptX Class Reference.prinln
self arg [stream]
prinln
operates in the same manner as prin
, except it also prints a newline character after the output. prin1
self [stream]
prin1
is equivalent to prin
with the @normal
option. The stream argument is optional and defaults to debug
.print
object [stream]
A combination of prinln
and prin1
, the print
function prints the object representation to stream with the @normal
option and a newline character. The stream argument is optional and defaults to debug
. See the discussion and examples that begin on page 73.prinString
object arg
prinString
yields a new String
instance containing a printed representation of the given object.printString
object
printString
is equivalent to prinString
, except that it forces the @normal
option.shortPrin
object arg stream length
shortPrin
is equivalent to prin
, except that shortPrin
prints only the number of characters specified by length. format
function:format
stream formatString object option
The format
global function prints a formatted string to a stream, where stream is the stream to print to, (for example, debug
), formatString is the string to print (which can include substitution characters), object is the object you want a printable representation of, and option is one of the four printing options, as described on page 74. The final argument is optional-if it is not supplied, it is passed as undefined
and defaults to @normal
.The stream and object arguments toThe formatString argument is a string that may contain substitution characters. Those substitution characters represent the object being printed, and are replaced in the resulting output by the printable representation of that object. For single objects, use "format
are in a different order than inprin
and its associated functions.
%*
" as a substitution character. i := 15
format debug "I is %*\n" i @normal
I is 15
Note that the format string can contain special characters such as newlines.
To print out a number of objects in one format string, you can put those objects in an array and use the array element substitution character. For multiple objects, the substitution character is "%n
" where n is the position of the element in the collection. The "%
" can be used as a terminator after n
. If you use this form for multiple elements in a collection, the option argument of the format expression must be a collection of options (such as an array), with a separate option for every element being printed.
format debug "%1 and %2% are dead\n" \
#("rosencrantz", "guildenstern") #(@unadorned,@unadorned)
rosencrantz and guildenstern are dead
As a shorthand for printing an array of options, the letters n
, c
, u
, and d
can be inserted after individual items. This allows items to be printed out with different formats. When individual formats are supplied, they override formats that are supplied in the fourth argument.
-- in this example, format codes %n1 and %u2 make the final
-- argument unnecessary
format debug "%n1 and %u2 are dead\n" #("rosencrantz", "guildenstern")
"rosencrantz" and guildenstern are dead
-- in this example, @unadorned overrides @debug for both items
format debug "%u1 and %u2 are dead\n" \
#("rosencrantz", "guildenstern") #(@debug,@debug)
rosencrantz and guildenstern are dead
If you use the "%*
" substitution in a format string on a collection object, the resulting output string contains the entire printable representation of that object:
format debug "The array is: %*" w @normal
The array is: #("rosencrantz", "guildenstern")
The "%n
" substitution only works on collections that implement the getNth
method. See Chapter 7, "Collections," or the "Collections" chapter of the ScriptX Components Guide for more information about collections. If you use the "%n
" substitution on objects that are not collections, ScriptX reports an exception.
keepOnGoing := #(1,2,3)
append keepOnGoing keepOnGoing
In this example, append
added the array keepOnGoing
to itself as its own fourth element. Without a special format to represent this condition, the printable representation of keepOnGoing
would go into an infinite loop trying to print its fourth element:
#(1, 2, 3, #(1, 2, 3, #(1, 2, 3, ...
Instead, keepOnGoing
prints using a special format that looks like this:
print keepOnGoing
#1=#(1, 2, 3, #1#)
In this format, the object that contains a reference to itself is specified by a number (#1
in this case), an equal sign, and the printable representation of itself. Then, in the list of elements, any elements that refer to that same object are indicated by that number, surrounded by hash signs (#1#
in this case).
Collections that contain multiple copies of the same object are printed using a recursive format:
x := "elbow"
b := #(x, x)
print b
#(#1="elbow", #1#)
In this example, the #1="elbow"
part refers to the first occurrence of x, and #1#
refers to all other occurrences.
In objects that contain multiple recursive or repeated objects, those collections are numbered consecutively:
a := "elbow"
b := "knee"
c := #(a, b, b, a)
print c
#(#2="elbow", #1="knee", #1#, #2#)
This document is part of the ScriptX Language Guide, one of the volumes of the ScriptX Technical Reference Series. ScriptX is developed by the ScriptX Engineering Team at Apple Computer, successor to the Kaleida Engineering Team at Kaleida Labs, Inc.